package com.clps.digital.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.ObjUtil;
import com.clps.digital.common.BaseResponse;
import com.clps.digital.common.ErrorCode;
import com.clps.digital.common.ResultUtils;
import com.clps.digital.dao.CurrencyDao;
import com.clps.digital.dao.OrderDao;
import com.clps.digital.dao.PropertyDao;
import com.clps.digital.dao.UserDao;
import com.clps.digital.model.entity.Currency;
import com.clps.digital.model.dto.Currency.TradeCurrency;
import com.clps.digital.model.entity.Orders;
import com.clps.digital.model.entity.Property;
import com.clps.digital.model.entity.User;
import com.clps.digital.model.vo.PropertyByCurrency;
import com.clps.digital.service.CurrencyService;
import com.clps.digital.util.UserContext;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @Author: 小炎子
 * @Date: 2024/9/2 上午11:10
 * @Description: $
 **/
public class CurrencyServiceImpl implements CurrencyService {

    private CurrencyDao currencyDao;

    private UserDao userDao;

    private PropertyDao propertyDao;

    private OrderDao orderDao;

    @Override
    public List<Currency> getCurrency() {
        return currencyDao.getCurrency();
    }

    @Override
    public BaseResponse<String> buyCurrency(TradeCurrency tradeCurrency) {
        Long userid = UserContext.getUser();
        Currency currency = currencyDao.getCurrencyById(tradeCurrency.getId());
        User user = userDao.getUser(userid);
        //判断余额
        if (isEnoughBalance(user,currency,tradeCurrency)){
            //执行金额扣减操作并更新余额并保持到数据库
            BigDecimal buyMoney = user.getUserBalance()
                    .subtract(currency.getPrice()
                            .multiply(tradeCurrency.getQuantity()));
            user.setUserBalance(buyMoney);
            userDao.saveUser(user);
            //判断法币库存
            if (isEnoughSale(currency, tradeCurrency)){
                //更新库存
                currency.setSale(currency.getSale()
                        .add(tradeCurrency.getQuantity()));
                currencyDao.saveCurrency(currency);
                //查询当前用户资产是否已经有此类法币，如有则修改数量，如没有则增加
                Property p = propertyDao.getByCurrencyProperty(userid,tradeCurrency.getId());
                if (ObjUtil.isEmpty(p)){
                    p = new Property();
                    //保存到个人资产表
                    p.setUserId(userid);
                    p.setCurrencyId(tradeCurrency.getId());
                    p.setQuantity(tradeCurrency.getQuantity());
                    propertyDao.addProperty(p);
                    //创建已完成的订单
                    Orders orders = new Orders();
                    orders.setBuyId(userid);
                    orders.setCurrencyId(tradeCurrency.getId());
                    orders.setQuantity(tradeCurrency.getQuantity());
                    orders.setPrice(currency.getPrice()
                            .multiply(tradeCurrency.getQuantity()));
                    orderDao.buysave(orders);
                    return ResultUtils.success("购买成功");
                }
                p.setQuantity(p.getQuantity().add(tradeCurrency.getQuantity()));
                propertyDao.updateProperty(p);
                //创建已完成的订单
                Orders orders = new Orders();
                orders.setBuyId(userid);
                orders.setCurrencyId(tradeCurrency.getId());
                orders.setQuantity(tradeCurrency.getQuantity());
                orders.setPrice(buyMoney);
                orderDao.buysave(orders);
                return ResultUtils.success("购买成功");
            }
            return ResultUtils.error(ErrorCode.OPERATION_ERROR,"法币超出预售量");
        }
        return ResultUtils.error(ErrorCode.OPERATION_ERROR,"余额不足");
    }

    @Override
    public BaseResponse<String> sellCurrency(TradeCurrency tradeCurrency) {
        Long userid = UserContext.getUser();
        Currency currency = currencyDao.getCurrencyById(tradeCurrency.getId());
        User user = userDao.getUser(userid);
        //找到对应userId和currencyId的那条记录
        Property property = propertyDao.getByCurrencyProperty(user.getId(),tradeCurrency.getId());
        //判断当前用户资产够不够出售
        if (isEnoughQuantity(userid,property,tradeCurrency)){
            //扣减用户余额
            BigDecimal sellMoney = user.getUserBalance()
                    .add(currency.getPrice()
                            .multiply(tradeCurrency.getQuantity()));
            user.setUserBalance(sellMoney);
            userDao.saveUser(user);
            //更新库存
            currency.setSale(currency.getSale()
                    .subtract(tradeCurrency.getQuantity()));
            currencyDao.saveCurrency(currency);
            //更新用户资产
            property.setQuantity(property.getQuantity().subtract(tradeCurrency.getQuantity()));
            propertyDao.updateProperty(property);
            //创建已完成的订单
            Orders orders = new Orders();
            orders.setSoldId(userid);
            orders.setCurrencyId(tradeCurrency.getId());
            orders.setQuantity(tradeCurrency.getQuantity());
            orders.setPrice(currency.getPrice()
                    .multiply(tradeCurrency.getQuantity()));
            orderDao.sellsave(orders);
            return ResultUtils.success("出售成功");
        }
        return ResultUtils.error(ErrorCode.OPERATION_ERROR,"您当前库存不足");
    }

    @Override
    public List<PropertyByCurrency> getProperty() {
        Long userId = UserContext.getUser();
        List<Property> propertyList = propertyDao.getProperty(userId);
        List<Currency> currencyList = new ArrayList<>();
        for (Property property : propertyList) {
            Long currencyId = property.getCurrencyId();
            currencyList.add(currencyDao.getCurrencyById(currencyId));
        }
        List<PropertyByCurrency> propertyByCurrencyList = BeanUtil.copyToList(propertyList, PropertyByCurrency.class);
        propertyByCurrencyList = propertyByCurrencyList.stream().map(propertyByCurrency -> {
            for (Currency currency : currencyList) {
                if (currency.getId().equals(propertyByCurrency.getCurrencyId())) {
                    BeanUtil.copyProperties(currency, propertyByCurrency,new String[]{"id"});
                }
            }
            return propertyByCurrency;
        }).collect(Collectors.toList());
        return propertyByCurrencyList;

    }

    @Override
    public BigDecimal getCurrencyNumber(BigDecimal bigDecimal,Long id) {
        Currency currency = currencyDao.getCurrencyById(id);
        BigDecimal num = bigDecimal.divide(currency.getPrice(),5,BigDecimal.ROUND_HALF_UP);
        return num;
    }


    /*
    * @Author 小炎子
    * @Description 判断当前用户余额是否充足
    * @Date 下午3:47 2024/9/2
    */
    public Boolean isEnoughBalance(User user, Currency currency, TradeCurrency tradeCurrency) {
        if (user.getUserBalance()
                .subtract(currency.getPrice()
                        .multiply(tradeCurrency.getQuantity()))
                .compareTo(BigDecimal.ZERO) >= 0){
            return true;
        }
        return false;
    }

    /*
    * @Author 小炎子
    * @Description 判断系统法币库存是否充足
    * @Date 下午3:32 2024/9/2
    */
    public Boolean isEnoughSale(Currency currency, TradeCurrency tradeCurrency) {
        int result = currency.getSale()
                .add(tradeCurrency.getQuantity())
                .compareTo(new BigDecimal(10000));
        if (result < 0){
            return true;
        }
        return false;
    }

    /*
    * @Author 小炎子
    * @Description 判断当前用户资产够不够出售
    * @Date 下午3:51 2024/9/2
    */
    public Boolean isEnoughQuantity(Long userid, Property property, TradeCurrency tradeCurrency) {
        List<Property> propertyList = propertyDao.getProperty(userid);
        for (Property p : propertyList) {
           if (p.getCurrencyId().equals(tradeCurrency.getId())) {
               if (p.getQuantity().subtract(tradeCurrency.getQuantity()).compareTo(BigDecimal.ZERO) >= 0){
                   return true;
               }
           }
        }
        return false;
    }
}
